
#include "remote_control.h"
#include "main.h"
#include "usart.h"

extern UART_HandleTypeDef huart1;
extern DMA_HandleTypeDef hdma_usart1_rx;

//遥控器控制变量
sbus_rc_t sbus_rc;
uint8_t   dbus_buf[DBUS_BUFLEN];
/**
  * @brief      enable global uart it and do not use DMA transfer done it
  * @param[in]  huart: uart IRQHandler id
  * @param[in]  pData: receive buff
  * @param[in]  Size:  buff size
  * @retval     set success or fail
  */
static int uart_receive_dma_no_it(UART_HandleTypeDef* huart, uint8_t* pData, uint32_t Size)
{
    uint32_t tmp1 = 0;

    tmp1 = huart->RxState;

    if (tmp1 == HAL_UART_STATE_READY)
    {
        if ((pData == NULL) || (Size == 0))
        {
            return HAL_ERROR;
        }

        huart->pRxBuffPtr = pData;
        huart->RxXferSize = Size;
        huart->ErrorCode  = HAL_UART_ERROR_NONE;

        /* Enable the DMA Stream */
        HAL_DMA_Start(huart->hdmarx, (uint32_t)&huart->Instance->DR, (uint32_t)pData, Size);

        /*
         * Enable the DMA transfer for the receiver request by setting the DMAR bit
         * in the UART CR3 register
         */
        SET_BIT(huart->Instance->CR3, USART_CR3_DMAR);

        return HAL_OK;
    }
    else
    {
        return HAL_BUSY;
    }
}

////接收原始数据，为25个字节，给了36个字节长度，防止DMA传输越界
//uint8_t sbus_rx_buf[2][SBUS_RX_BUF_NUM];
//
//void remote_control_init(void)
//{
//    RC_init(sbus_rx_buf[0], sbus_rx_buf[1], SBUS_RX_BUF_NUM);
//}
//
//const SBUS_ctrl_t *get_remote_control_point(void)
//{
//    return &sbus_ctrl;
//}

//////串口中断
//void USART1_IRQHandler(void)
//{
//    if(huart1.Instance->SR & UART_FLAG_RXNE)//接收到数据
//    {
//        __HAL_UART_CLEAR_PEFLAG(&huart1);
//        sbus_to_rc(sbus_rx_buf[0], &sbus_ctrl);
//    }
//    else if(USART3->SR & UART_FLAG_IDLE)
//    {
//        static uint16_t this_time_rx_len = 0;
//
//        __HAL_UART_CLEAR_PEFLAG(&huart1);
//
//        if ((hdma_usart1_rx.Instance->CR & DMA_SxCR_CT) == RESET)
//        {
//            /* Current memory buffer used is Memory 0 */
//
//            //disable DMA
//            //失效DMA
//            __HAL_DMA_DISABLE(&hdma_usart1_rx);
//
//            //get receive data length, length = set_data_length - remain_length
//            //获取接收数据长度,长度 = 设定长度 - 剩余长度
//            this_time_rx_len = SBUS_RX_BUF_NUM - hdma_usart1_rx.Instance->NDTR;
//
//            //reset set_data_length
//            //重新设定数据长度
//            hdma_usart1_rx.Instance->NDTR = SBUS_RX_BUF_NUM;
//
//            //set memory buffer 1
//            //设定缓冲区1
//            hdma_usart1_rx.Instance->CR |= DMA_SxCR_CT;
//
//            //enable DMA
//            //使能DMA
//            __HAL_DMA_ENABLE(&hdma_usart1_rx);
//
//            if(this_time_rx_len == RC_FRAME_LENGTH)
//            {
//                sbus_to_rc(sbus_rx_buf[0], &sbus_ctrl);
//            }
//        }
//        else
//        {
//            /* Current memory buffer used is Memory 1 */
//            //disable DMA
//            //失效DMA
//            __HAL_DMA_DISABLE(&hdma_usart1_rx);
//
//            //get receive data length, length = set_data_length - remain_length
//            //获取接收数据长度,长度 = 设定长度 - 剩余长度
//            this_time_rx_len = SBUS_RX_BUF_NUM - hdma_usart1_rx.Instance->NDTR;
//
//            //reset set_data_length
//            //重新设定数据长度
//            hdma_usart1_rx.Instance->NDTR = SBUS_RX_BUF_NUM;
//
//            //set memory buffer 0
//            //设定缓冲区0
//            DMA1_Stream1->CR &= ~(DMA_SxCR_CT);
//
//            //enable DMA
//            //使能DMA
//            __HAL_DMA_ENABLE(&hdma_usart1_rx);
//
//            if(this_time_rx_len == RC_FRAME_LENGTH)
//            {
//                //处理遥控器数据
//                sbus_to_rc(sbus_rx_buf[1], &sbus_ctrl);
//            }
//        }
//    }
//}
//
//void sbus_to_rc(volatile const uint8_t *sbus_buf, SBUS_ctrl_t *sbusCtrl)
//{
//    if(sbus_buf[0]==0x0f)
//    {
//        sbusCtrl->ch[0]  =(int16_t)                         (((sbus_buf[1] | sbus_buf[2] << 8) & 0x07FF) - 1024);
//        sbusCtrl->ch[1]  =(int16_t)                    (((sbus_buf[2] >> 3 | sbus_buf[3] << 5) & 0x07FF) - 1024);
//        sbusCtrl->ch[2]  =(int16_t)(((sbus_buf[3] >> 6 | sbus_buf[4] << 2 | sbus_buf[5] << 10) & 0x07FF) - 1024);
//        sbusCtrl->ch[3]  =(int16_t)                    (((sbus_buf[5] >> 1 | sbus_buf[6] << 7) & 0x07FF) - 1024);
//        sbusCtrl->ch[4]  =(int16_t)                    (((sbus_buf[6] >> 4 | sbus_buf[7] << 4) & 0x07FF) - 1024);
//        sbusCtrl->sw[0]  =(int16_t)(((sbus_buf[7] >> 7 | sbus_buf[8] << 1  | sbus_buf[9] << 9) & 0x07FF) - 1024);
//        sbusCtrl->sw[1]  =(int16_t)                   (((sbus_buf[9] >> 2 | sbus_buf[10] << 6) & 0x07FF) - 1024);
//    }
//    else
//    {
//        sbusCtrl->ch[0] = 404;
//        sbusCtrl->ch[1] = 404;
//    }
//}
void sbusPreparePacket(uint8_t *buff)
{
    if(buff[0]==0x0f)
    {
        sbus_rc.ch[0]  =(((buff[1]    |buff[2]<<8)                   &0x07FF) -1024);
        sbus_rc.ch[1]  =(((buff[2]>>3 |buff[3]<<5)                   &0x07FF) -1024);
        sbus_rc.ch[2]  =(((buff[3]>>6 |buff[4]<<2  |buff[5]<<10)     &0x07FF) -1024);
        sbus_rc.ch[3]  =(((buff[5]>>1 |buff[6]<<7)                   &0x07FF) -1024);
        sbus_rc.ch[4]  =(((buff[6]>>4 |buff[7]<<4)                   &0x07FF) -1024);
        sbus_rc.sw[0]  =(((buff[7]>>7 |buff[8]<<1  |buff[9]<<9)      &0x07FF) -1024);
        sbus_rc.sw[1]  =(((buff[9]>>2 |buff[10]<<6)                  &0x07FF) -1024);
        //SBUS_channels[7]  =(((buff[10]>>5|buff[11]<<3)                  &0x07FF) -992);

        /*
        SBUS_channels[0]  =(((buff[1]    |buff[2]<<8)                   &0x07FF) -1024);
        SBUS_channels[1]  =(((buff[2]>>3 |buff[3]<<5)                   &0x07FF) -1024);
        SBUS_channels[2]  =(((buff[3]>>6 |buff[4]<<2  |buff[5]<<10)     &0x07FF) -1024);
        SBUS_channels[3]  =(((buff[5]>>1 |buff[6]<<7)                   &0x07FF) -1024);
        SBUS_channels[4]  =(((buff[6]>>4 |buff[7]<<4)                   &0x07FF) -1024);
        SBUS_channels[5]  =(((buff[7]>>7 |buff[8]<<1  |buff[9]<<9)      &0x07FF) -1024);
        SBUS_channels[6]  =(((buff[9]>>2 |buff[10]<<6)                  &0x07FF) -1024);
        SBUS_channels[7]  =(((buff[10]>>5|buff[11]<<3)                  &0x07FF) -992);
        */
//        SBUS_channels[8]  =(((buff[12]   |buff[13]<<8)                  &0x07FF) -992);
//        SBUS_channels[9]  =(((buff[13]>>3|buff[14]<<5)                  &0x07FF) -992);
//        SBUS_channels[10] =(((buff[14]>>6|buff[15]<<2 |buff[16]<<10)    &0x07FF) -992);
//        SBUS_channels[11] =(((buff[16]>>1|buff[17]<<7)                  &0x07FF) -992);
//        SBUS_channels[12] =(((buff[17]>>4|buff[18]<<4)                  &0x07FF) -992);
//        SBUS_channels[13] =(((buff[18]>>7|buff[19]<<1 |buff[16]<<10)    &0x07FF) -992);
//        SBUS_channels[14] =(((buff[20]>>2|buff[21]<<6)                  &0x07FF) -992);
//        SBUS_channels[15] =(((buff[21]>>5|buff[22]<<3)                  &0x07FF) -992);
    }
    else
    {
        sbus_rc.ch[4] = 404;
        //SBUS_channels[3] = 404;
    }
}

/**
  * @brief   initialize dbus uart device
  * @param
  * @retval
  */
void dbus_uart_init(void)
{
    /* open uart idle it */
    __HAL_UART_CLEAR_IDLEFLAG(&DBUS_HUART);
    __HAL_UART_ENABLE_IT(&DBUS_HUART, UART_IT_IDLE);

    uart_receive_dma_no_it(&DBUS_HUART, dbus_buf, DBUS_MAX_LEN);
}
uint16_t dma_current_data_counter(DMA_Stream_TypeDef *dma_stream)
{
    /* Return the number of remaining data units for DMAy Streamx */
    return ((uint16_t)(dma_stream->NDTR));
}

/**
  * @brief      clear idle it flag after uart receive a frame data
  * @param[in]  huart: uart IRQHandler id
  * @retval
  */
static void uart_rx_idle_callback(UART_HandleTypeDef* huart)
{
    /* clear idle it flag avoid idle interrupt all the time */
    __HAL_UART_CLEAR_IDLEFLAG(huart);

    /* handle received data in idle interrupt */
    if (huart == &DBUS_HUART)
    {
        /* clear DMA transfer complete flag */
        __HAL_DMA_DISABLE(huart->hdmarx);

        /* handle dbus data dbus_buf from DMA */
        if ((DBUS_MAX_LEN - dma_current_data_counter(huart->hdmarx->Instance)) == DBUS_BUFLEN)
        {
            //rc_callback_handler(&rc, dbus_buf);
            sbusPreparePacket(dbus_buf);
        }

        /* restart dma transmission */
        __HAL_DMA_SET_COUNTER(huart->hdmarx, DBUS_MAX_LEN);
        __HAL_DMA_ENABLE(huart->hdmarx);
    }
}

/**
  * @brief      callback this function when uart interrupt
  * @param[in]  huart: uart IRQHandler id
  * @retval
  */
void uart_receive_handler(UART_HandleTypeDef *huart)
{
    if (__HAL_UART_GET_FLAG(huart, UART_FLAG_IDLE) &&
        __HAL_UART_GET_IT_SOURCE(huart, UART_IT_IDLE))
    {
        uart_rx_idle_callback(huart);
        sbusPreparePacket(dbus_buf);
    }
}